<template>
  <div class="large-point-map">
    <div id="large-point-map" class="map-container"></div>
    <div class="map-controls">
      <div class="zoom-info">当前缩放级别: {{ currentZoom }}</div>
    </div>
    <div
      v-if="hoverInfo"
      class="hover-info"
      :style="{ left: hoverInfo.x + 'px', top: hoverInfo.y + 'px' }"
    >
      {{ hoverInfo.text }}
    </div>
  </div>
</template>

<script setup lang="ts">
import { ref, onMounted, onUnmounted } from 'vue';
import Map from 'ol/Map';
import View from 'ol/View';
import TileLayer from 'ol/layer/Tile';
import XYZ from 'ol/source/XYZ';
import { fromLonLat } from 'ol/proj';
import { defaults as defaultControls } from 'ol/control';
import WebGLPointsLayer from 'ol/layer/WebGLPoints';
import VectorSource from 'ol/source/Vector';
import Feature from 'ol/Feature';
import Point from 'ol/geom/Point';
import BaseEvent from 'ol/events/Event';

// 地图实例
let map: Map | null = null;
let baseLayer: TileLayer<XYZ> | null = null;
let pointLayer: WebGLPointsLayer<VectorSource> | null = null;

// 当前缩放级别和悬停信息
const currentZoom = ref(0);
const hoverInfo = ref<{ x: number; y: number; text: string } | null>(null);

// 生成随机点数据
const generateRandomPoints = (count: number) => {
  const features = [];
  const center = fromLonLat([114.30, 30.50]); // 武汉中心点
  const radius = 50000; // 50公里半径

  for (let i = 0; i < count; i++) {
    const angle = Math.random() * Math.PI * 2;
    const distance = Math.random() * radius;
    const x = center[0] + Math.cos(angle) * distance;
    const y = center[1] + Math.sin(angle) * distance;

    const feature = new Feature({
      geometry: new Point([x, y]),
      properties: {
        id: i + 1,
        name: `点 ${i + 1}`,
      },
    });

    features.push(feature);
  }

  return features;
};

// 初始化地图
onMounted(() => {
  // 创建底图图层
  baseLayer = new TileLayer({
    source: new XYZ({
      url: 'http://wprd0{1-4}.is.autonavi.com/appmaptile?lang=zh_cn&size=1&scale=1&style=7&x={x}&y={y}&z={z}',
    }),
  });

  // 创建地图实例
  map = new Map({
    target: 'large-point-map',
    layers: [baseLayer],
    view: new View({
      center: fromLonLat([114.30, 30.50]),
      zoom: 10,
      projection: 'EPSG:3857',
    }),
    controls: defaultControls().extend([]),
  });

  // 生成随机点数据
  const features = generateRandomPoints(500000);
  const source = new VectorSource({ features });

  // 创建 WebGL 点图层
  pointLayer = new WebGLPointsLayer({
    source,
    style: {
      'circle-radius': 3,
      'circle-fill-color': 'rgba(255,0,0,0.5)',
    },
    disableHitDetection: true,
  });

  map.addLayer(pointLayer);

  // 监听缩放级别变化
  map.getView().on('change:resolution', () => {
    currentZoom.value = Math.round(map!.getView().getZoom()!);
  });

  // 添加鼠标悬停交互
  map.on('pointermove', (evt: BaseEvent) => {
    const e = evt as unknown as { pixel: number[]; originalEvent: MouseEvent };
    if (map && pointLayer) {
      const feature = map.forEachFeatureAtPixel(e.pixel, (f) => f);
      if (feature) {
        hoverInfo.value = {
          x: e.originalEvent.clientX + 10,
          y: e.originalEvent.clientY - 10,
          text: `点 ${feature.get('properties').id}`,
        };
      } else {
        hoverInfo.value = null;
      }
    }
  });
});

// 清理资源
onUnmounted(() => {
  if (map) {
    map.setTarget(undefined);
    map = null;
  }
});
</script>

<style scoped>
.large-point-map {
  width: 100%;
  height: 100%;
  position: relative;
}

.map-container {
  width: 100%;
  height: 100%;
}

.map-controls {
  position: absolute;
  top: 10px;
  right: 10px;
  background: rgba(255, 255, 255, 0.8);
  padding: 5px 10px;
  border-radius: 4px;
  z-index: 1000;
}

.zoom-info {
  font-size: 14px;
  color: #333;
}

.hover-info {
  position: absolute;
  background: rgba(0, 0, 0, 0.7);
  color: #fff;
  padding: 4px 8px;
  border-radius: 4px;
  font-size: 12px;
  pointer-events: none;
  z-index: 1000;
  white-space: nowrap;
}
</style> 